﻿using System;
using System.Linq;
using System.Collections.Generic;
using System.Windows.Forms;
using Microsoft.WindowsMobile;
using Microsoft.WindowsMobile.Status;
using Microsoft.Win32;
using System.Threading;
using System.Diagnostics;
using System.Runtime.InteropServices;
//using Microsoft.WindowsCE.Forms;

namespace InCall_Lock
{
    public static class Program
    {
        #region Common variables
        public static RegistryKey programStateKey = Registry.LocalMachine.OpenSubKey(@"System\State\InCall Lock", true);
        public static RegistryKey systemStateKey = Registry.LocalMachine.OpenSubKey(@"System\State", true);
        public static int thisPID = Process.GetCurrentProcess().Id;
        #endregion

        #region P/Invoke declarations
        [DllImport("coredll.dll")]
        public static extern IntPtr SetCursor(IntPtr hCursor);
        [DllImport("coredll.dll", EntryPoint = "keybd_event", SetLastError = true)]
        internal static extern void keybd_event(byte bVk, byte bScan, int dwFlags, int dwExtraInfo);
        #endregion
        public static HookKeys hook = new HookKeys();
        public static bool overrideDefault;
        public static int clickNumber = 1;
        public static int timeLimit = 0;
        private static int dblClickTimeout = 500;
        public static void HookEvent(HookEventArgs e, KeyBoardInfo keyBoardInfo)
        {
            overrideDefault = true;
            //clickNumber = 1;
            //programStateKey.SetValue("KeyPress", keyBoardInfo.vkCode);
            //programStateKey.SetValue("ScanCode", keyBoardInfo.scanCode);
            //programStateKey.SetValue("Time", keyBoardInfo.time);
            //programStateKey.SetValue("Flags", keyBoardInfo.flags);
            switch (keyBoardInfo.vkCode)
            {
                case 117:
                    overrideDefault = false;
                    break;
                case 118:
                    overrideDefault = false;
                    break;
                case 114:
                    switch ((int)e.wParam)
                    {
                        //
                        case 256:
                            if (clickNumber > 1)
                            {
                                if ((keyBoardInfo.time - timeLimit) <= dblClickTimeout)
                                {
                                    overrideDefault = false;
                                }
                                else
                                    clickNumber = 1;
                            }
                            break;
                        case 257:
                            switch (clickNumber)
                            {
                                //
                                case 1:
                                    clickNumber = 2;
                                    timeLimit = keyBoardInfo.time + dblClickTimeout;
                                    break;
                                case 2:
                                    overrideDefault = false;
                                    clickNumber = 1;
                                    break;
                            }
                            break;
                    }
                    //
                    //overrideDefault = !ProcessKey.isDoubleClick();
                    //if ((int)e.wParam == 257)
                    //    ProcessKey.nextClickTime = DateTime.Now.AddMilliseconds(500);
                    break;
                default:
                    overrideDefault = true;
                    break;
            }

        }

        /// <summary>
        /// The main entry point for the application.
        /// </summary>
        [MTAThread]
        public static void Main()
        {
            SetCursor(IntPtr.Zero);
            //Log.logEnabled = true;
            //Log.Start("incalllog.txt", -1);
            //Thread.Sleep(500);
            CheckIfRunning();
            programStateKey.SetValue("LastPID", thisPID);
            SystemState callReceived = new SystemState(SystemProperty.PhoneIncomingCall, false);
            callReceived.Changed += new ChangeEventHandler(CallReceived_Changed);
            //Program prog = new Program();
            //HookKeys hook = new HookKeys();
            //ProcessKey.nextClickTime = DateTime.Now;
            hook.HookEvent += new HookKeys.HookEventHandler(HookEvent);
        }
        /*public static void HookEvent()
        {
            MessageBox.Show("Key pressed!");
        }*/
        static void CheckIfRunning()
        {
            if (programStateKey == null)
            {
                systemStateKey.CreateSubKey("InCall Lock");
                try
                {
                    programStateKey = Registry.LocalMachine.OpenSubKey(@"System\State\InCall Lock", true);
                }
                catch
                {
                    Registry.LocalMachine.CreateSubKey(@"System\State\InCall Lock");
                    programStateKey = Registry.LocalMachine.OpenSubKey(@"System\State\InCall Lock", true);
                }
                programStateKey.SetValue("Lock", 0);
                programStateKey.SetValue("LastPID", 0);
            }

            int lastPID = 0;
            try
            {
                lastPID = (int)programStateKey.GetValue("LastPID");
            }
            catch
            {
                programStateKey.SetValue("LastPID", 0);
            }
            if (lastPID != 0)
            {
                //MessageBox.Show("Running process will be killed");
                try
                {
                    Process runningProcess = Process.GetProcessById(lastPID);
                    runningProcess.Kill();
                    programStateKey.SetValue("LastPID", 0);
                    //MessageBox.Show("Process killed. Exiting. ");
                    MessageBox.Show("InCall Lock disabled");
                    Process.GetCurrentProcess().Kill();

                }
                catch
                {
                    //MessageBox.Show("Process isn't running. Starting InCall Lock");
                }
            }
        }

        public static void CheckIncoming()
        {
            bool incomingCall = SystemState.PhoneIncomingCall;
            //bool isLockEnabled = (int)systemStateKey.GetValue("Lock") > 0 ? true : false;
            bool isButtonsLocked = (int)programStateKey.GetValue("Lock") > 0 ? true : false;
            //HookKeys hook = new HookKeys(hook.Start);
            //hook.HookEvent += new HookKeys.HookEventHandler(hook.HookEvent);
            if (incomingCall)
            {
                //if (isLockEnabled)
                //{
                    //MessageBox.Show("Call received. Disabling buttons");
                    programStateKey.SetValue("Lock", 1);
                    //RegisterRecordKey(msgWindowHandle);
                    hook.Start(); 
                    
                //}
                //else
                    //MessageBox.Show("Device unlocked, no action");
            }
            else
            {
                if (isButtonsLocked)
                {
                    //MessageBox.Show("Call picked up/dropped. Enabling buttons");
                    programStateKey.SetValue("Lock", 0);
                    //RegisterBackToCProg();
                    hook.Stop();
                }
                //else
                    //MessageBox.Show("Buttons unlocked, no action");
            }
        }

        static void CallReceived_Changed(object sender, ChangeEventArgs args)
        {
            //MessageBox.Show("Event triggered");
            CheckIncoming();
            //SetNotifications();
        }
    }
}